window.IOFactory = new function() {
		
	var sockets = [];
	var ef = null;
		
	/*
	 * TITTSocket
	 */
	//tidy for IE
	window.onunload = function() {
		for(var i = 0; i < sockets.length; i++)
			sockets[i].close();
	}
	
	function findSocket() {
		for(var i = 0; i < sockets.length; i++) {
			if(sockets[i].isClosed)
				return sockets[i]; 
		}
		sockets[sockets.length] = new TITTSocket();
		return sockets[sockets.length-1];
	}
	
	this.createTITTSocket = function() {
		var sock = findSocket();
		sock.isClosed = false;
		return sock;
	}
			
	/*
	 * Encoders / Decoders here
	 */
	
	this.createEncoder = function() {
		return new CompositeEncoder([new ArrayEncoder(new AsStringEncoder()), new ObjectEncoder(), new VoidEncoder()]);
	}
	
	this.createDecoder = function() {
		return new CompositeDecoder([new ArrayDecoder(new AsStringDecoder()), new ObjectDecoder(), new VoidDecoder()]);
	}
	
	
	/*
	 * HeaderWriters / HeaderReaders here
	 */
	
	/*
	 * Facades here
	 */
	 
	this.createEncodingFacade = function() {
		if(ef) return ef;
		
		ef = new function() {
			var e = IOFactory.createEncoder();
			var d = IOFactory.createDecoder();

			this.encode = function(t,o) {
				return e.encode(t,o);
			}
			this.isEncodeable = function(t) {
				return e.isEncodeable(t);
			}
			this.decode = function(t,e) {
				return d.decode(t,e);
			}
			this.isDecodeable = function(t) {
				return d.isDecodeable(t);
			}
		}
		
		return ef;
	}
	
}

